package dao.impl;

import dao.BaseDao;
import dao.ClockRuleDao;
import entity.ClockRule;

import java.sql.*;
import java.time.LocalTime;
import java.util.ArrayList;
import java.util.List;

public class ClockRuleDaoImpl extends BaseDao implements ClockRuleDao {

    @Override
    public List<ClockRule> findAll() throws SQLException, ClassNotFoundException {
        getConnection();
        Statement stmt = null;
        ResultSet rs = null;
        List<ClockRule> rules = new ArrayList<>();

        try {

            String sql = "SELECT * FROM clock_urle";
            stmt = conn.createStatement();
            rs = stmt.executeQuery(sql);

            while (rs.next()) {
                rules.add(extractRuleFromResultSet(rs));
            }
            return rules;
        } finally {
            if (rs != null) rs.close();
            if (stmt != null) stmt.close();
            if (conn != null) conn.close();
        }
    }

    @Override
    public List<ClockRule> findActiveRules() throws SQLException, ClassNotFoundException {
        getConnection();
        Statement stmt = null;
        ResultSet rs = null;
        List<ClockRule> rules = new ArrayList<>();

        try {

            String sql = "SELECT * FROM clock_urle WHERE active = 1";
            stmt = conn.createStatement();
            rs = stmt.executeQuery(sql);

            while (rs.next()) {
                rules.add(extractRuleFromResultSet(rs));
            }
            return rules;
        } finally {
            if (rs != null) rs.close();
            if (stmt != null) stmt.close();
            if (conn != null) conn.close();
        }
    }

    @Override
    public ClockRule findById(Integer id) throws SQLException, ClassNotFoundException {
        getConnection();
        PreparedStatement pstmt = null;
        ResultSet rs = null;

        try {

            String sql = "SELECT * FROM clock_urle WHERE id = ?";
            pstmt = conn.prepareStatement(sql);
            pstmt.setInt(1, id);
            rs = pstmt.executeQuery();

            if (rs.next()) {
                return extractRuleFromResultSet(rs);
            }
            return null;
        } finally {
            if (rs != null) rs.close();
            if (pstmt != null) pstmt.close();
            if (conn != null) conn.close();
        }
    }

    @Override
    public boolean save(ClockRule rule) throws SQLException, ClassNotFoundException {
        getConnection();
        PreparedStatement pstmt = null;
        ResultSet rs = null;

        try {

            String sql = "INSERT INTO clock_urle (urle_name, start_time, end_time, active) VALUES (?, ?, ?, ?)";
            pstmt = conn.prepareStatement(sql, Statement.RETURN_GENERATED_KEYS);

            pstmt.setString(1, rule.getName());
            pstmt.setTime(2, Time.valueOf(rule.getStartTime()));
            pstmt.setTime(3, Time.valueOf(rule.getEndTime()));
            pstmt.setBoolean(4, rule.getActive());

            int affectedRows = pstmt.executeUpdate();
            if (affectedRows > 0) {
                rs = pstmt.getGeneratedKeys();
                if (rs.next()) {
                    rule.setId(rs.getInt(1));
                }
                return true;
            }
            return false;
        } finally {
            if (rs != null) rs.close();
            if (pstmt != null) pstmt.close();
            if (conn != null) conn.close();
        }
    }

    @Override
    public boolean update(ClockRule rule) throws SQLException, ClassNotFoundException {
        getConnection();
        PreparedStatement pstmt = null;

        try {

            String sql = "UPDATE clock_urle SET urle_name = ?, start_time = ?, end_time = ?, active = ? WHERE id = ?";
            pstmt = conn.prepareStatement(sql);

            pstmt.setString(1, rule.getName());
            pstmt.setTime(2, Time.valueOf(rule.getStartTime()));
            pstmt.setTime(3, Time.valueOf(rule.getEndTime()));
            pstmt.setBoolean(4, rule.getActive());
            pstmt.setInt(5, rule.getId());

            return pstmt.executeUpdate() > 0;
        } finally {
            if (pstmt != null) pstmt.close();
            if (conn != null) conn.close();
        }
    }

    @Override
    public boolean delete(Integer id) throws SQLException, ClassNotFoundException {
       getConnection();
        PreparedStatement pstmt = null;

        try {

            String sql = "DELETE FROM clock_urle WHERE id = ?";
            pstmt = conn.prepareStatement(sql);
            pstmt.setInt(1, id);

            return pstmt.executeUpdate() > 0;
        } finally {
            if (pstmt != null) pstmt.close();
            if (conn != null) conn.close();
        }
    }

    @Override
    public boolean toggleStatus(Integer id, Boolean active) throws SQLException, ClassNotFoundException {
       getConnection();
        PreparedStatement pstmt = null;

        try {

            String sql = "UPDATE clock_urle SET active = ? WHERE id = ?";
            pstmt = conn.prepareStatement(sql);
            pstmt.setBoolean(1, active);
            pstmt.setInt(2, id);

            return pstmt.executeUpdate() > 0;
        } finally {
            if (pstmt != null) pstmt.close();
            if (conn != null) conn.close();
        }
    }

    public ClockRule extractRuleFromResultSet(ResultSet rs) throws SQLException {
        ClockRule rule = new ClockRule();
        rule.setId(rs.getInt("id"));
        rule.setName(rs.getString("urle_name"));
        rule.setStartTime(rs.getTime("start_time").toLocalTime());
        rule.setEndTime(rs.getTime("end_time").toLocalTime());
        rule.setActive(rs.getBoolean("active"));
        return rule;
    }
}